function TransactionSource(transactions) {

	this.datatype = 'array';
	this.localdata = transactions;
	this.totalrecords = transactions.length;
	this.datafields = [
		{ name: 'id', type: 'number' },
		{ name: 'date', type: 'date' },
		{ name: 'approved', type: 'boolean' },
		{ name: 'delta', type: 'int' },
		{ name: 'srcCombo', type: 'string' },
		{ name: 'srcSum', type: 'number' },
		{ name: 'srcCur', type: 'string' },
		{ name: 'dstAccount', type: 'string' },
		{ name: 'dstSum', type: 'number' },
		{ name: 'dstCur', type: 'string' },
		{ name: 'category', type: 'string' },
		{ name: 'tags', type: 'string' },
		{ name: 'desc', type: 'string' }
	];
	this.id = 'id';
};

function TrSource() {
	var self = this;
	this.datatype = "json";
	this.datafields = [
		{ name: 'date', type: 'date' },
		{ name: 'approved', type: 'boolean' },
		{ name: 'delta', type: 'int' },
		{ name: 'srcCombo', type: 'string' },
		{ name: 'srcSum', type: 'number' },
		{ name: 'srcCur', type: 'string' },
		{ name: 'dstAccount', type: 'string' },
		{ name: 'dstSum', type: 'number' },
		{ name: 'dstCur', type: 'string' },
		{ name: 'category', type: 'string' },
		{ name: 'tags', type: 'string' },
		{ name: 'desc', type: 'string' }
	];
	this.root = 'items';
	this.id = 'id';
	this.url = 'service/transactions/read.txt';
	this.type = 'POST';
	this.beforeprocessing = function (data) {
		self.totalrecords = data.total;
	}
};

var cellsrenderer = function(row, column, value, defaultHtml, columnSettings, rowData) {
	var color = 'darkblue';
	if (rowData.delta < 0) {
		color = 'darkred';
	} else if (rowData.delta > 0) {
		color = 'darkgreen';
	}
	var element = $(defaultHtml);
	element.css({ 'color': color });
	return element[0].outerHTML;
	return defaultHtml;
};

function TransactionsGrid(gridId) {

    this.gridId = gridId;

    this.getCurrencies = function(items, getter) {
        var currencies = new Array();
        var curSet = {}
        ko.utils.arrayForEach(items, function(item) {
            var cur = getter(item);
            if(cur != null) {
                curSet[cur] = true;
            }
        });
        for(var cur in curSet) {
            currencies.push(cur);
        }
        return currencies;
    };

    this.getSrcCurrencies = function(items) {
        return this.getCurrencies(items, function (item) {
            return item.srcCur;
        });
    };

    this.getDstCurrencies = function(items) {
        return this.getCurrencies(items, function (item) {
            return item.dstCur;
        });
    };

    this.getSrcAggregates = function(items) {
        var currencies = new Array();
        var map = {};
        ko.utils.arrayForEach(items, function(item) {
            if(!(item.srcCur in map) && item.srcCur != null) {
                var cur = {};
                cur['<b>' + item.srcCur + '</b>'] = function(aggregatedValue, currentValue, column, record) {
                    if(record['srcCur'] === item.srcCur && item.srcCur != null) {
                        return aggregatedValue + currentValue;
                    }
                    return aggregatedValue;
                }
                currencies.push(cur);
                map[item.srcCur] = true;
            }
        });
        return currencies;
    };

    this.getDstAggregates = function(items) {
        var currencies = new Array();
        var map = {};
        ko.utils.arrayForEach(items, function(item) {
            if(!(item.dstCur in map) && item.dstCur != null) {
                var cur = {};
                cur['<b>' + item.dstCur + '</b>'] = function(aggregatedValue, currentValue, column, record) {
                    if(record['dstCur'] === item.dstCur && item.dstCur != null) {
                        return aggregatedValue + currentValue;
                    }
                    return aggregatedValue;
                }
                currencies.push(cur);
                map[item.srcCur] = true;
            }
        });
        return currencies;
    };

    this.init = function (source) {
        $(this.gridId).jqxGrid(
            {
                width: '99.5%',
                source: source,
                selectionmode: 'none',
                editmode: 'selectedrow',
                editable: true,
                enabletooltips: true,
                altrows: true,
                virtualmode: true,
                pageable: true,
                pagesizeoptions: ['2', '10', '15', '20', '30', '50', '100'],
                pagesize: 20,
                rendergridrows: function () {
                    return source.records;
                },
                showstatusbar: true,
                showaggregates: true
            });
    };

    this.update = function (source) {
        $(this.gridId).jqxGrid({ source: source });
    };

    this.render = function (transactions) {
        var srcCurCount = this.getSrcCurrencies(transactions).length;
        var dstCurCount = this.getDstCurrencies(transactions).length;
        $(this.gridId).jqxGrid(
            {
                statusbarheight: 22 * Math.max(srcCurCount, dstCurCount),
                columns: [
                    { text: ' ', datafield: 'approved', columntype: 'checkbox', width: '2%' },
                    { text: 'Дата', datafield: 'date', columntype: 'datetimeinput', cellsformat: 'dd.MM.yyyy', width: '8%', minwidth: 80 },
                    { text: 'Счет', columngroup: 'src', datafield: 'srcCombo', width: '10%' },
                    { text: 'Сумма', columngroup: 'src', datafield: 'srcSum', width: '10%', cellsformat: 'f2', cellsalign: 'right', aggregates: this.getSrcAggregates(transactions || []), cellsrenderer: cellsrenderer },
                    { text: 'В', columngroup: 'src', datafield: 'srcCur', width: '3%' },
                    { text: 'Счет', columngroup: 'dst', datafield: 'dstAccount', width: '10%' },
                    { text: 'Сумма', columngroup: 'dst', datafield: 'dstSum', width: '10%', cellsformat: 'f2', cellsalign: 'right', aggregates: this.getDstAggregates(transactions || []), cellsrenderer: cellsrenderer },
                    { text: 'В', columngroup: 'dst', datafield: 'dstCur', width: '3%' },
                    { text: 'Категория', datafield: 'category', width: '17%' },
                    { text: 'Теги', datafield: 'tags', width: '10%' },
                    { text: 'Описание', datafield: 'desc', width: '17%' }
                ],
                columngroups: [
                    { text: 'Списание', align: 'center', name: 'src' },
                    { text: 'Зачисление', align: 'center', name: 'dst' }
                ]
            });
    };
};